package com.xuyh.logonline.filter;

import ch.qos.logback.classic.Level;
import ch.qos.logback.classic.Logger;
import ch.qos.logback.classic.turbo.TurboFilter;
import ch.qos.logback.core.spi.FilterReply;
import com.alibaba.fastjson.JSON;
import com.xuyh.logonline.config.LogOnlineWebSocket;
import com.xuyh.logonline.dto.LoggerMessage;
import com.xuyh.logonline.properties.LogOnlineProperties;
import lombok.AllArgsConstructor;
import org.joda.time.DateTime;
import org.slf4j.Marker;
import org.springframework.util.StringUtils;

/**
 * @author xuyh
 * @date 2019年1月8日 20:25:00
 * @description 日志过滤器
 */

@AllArgsConstructor
public class LogOnlineFilter extends TurboFilter {


    private LogOnlineWebSocket logOnlineWebSocket;
    private LogOnlineProperties logOnlineProperties;


    @Override
    public FilterReply decide(Marker marker, Logger logger, Level level, String s, Object[] objects, Throwable throwable) {
        //连接的人数，不少于1人，将日志发送
        if (LogOnlineWebSocket.getOnlineCount().get() != 0) {
            if (!this.validateLevel(level)) {
                return FilterReply.ACCEPT;
            }
            if (!validateClassName(logger)) {
                return FilterReply.ACCEPT;
            }
            LoggerMessage loggerMessage = new LoggerMessage();
            loggerMessage.setBody(s + "---->" + JSON.toJSONString(objects));
            loggerMessage.setClassName(logger.getName());
            loggerMessage.setLevel(level.levelStr);
            loggerMessage.setThreadName(Thread.currentThread().getName());
            loggerMessage.setTimestamp(DateTime.now().toString("yyyy-MM-dd HH:mm:ss SSS"));
            logOnlineWebSocket.sendAll(JSON.toJSONString(loggerMessage));
        }
        return FilterReply.ACCEPT;
    }


    /**
     * 判断 等级是否存在
     *
     * @param level 等级
     * @return boolean
     */
    private boolean validateLevel(Level level) {


        String[] levels = logOnlineProperties.getLevel();
        if (levels == null || levels.length == 0) {
            return true;
        }

        String levelStr = level.levelStr;

        for (String tmp : levels) {
            if (levelStr.equalsIgnoreCase(tmp)) {
                return true;
            }
        }
        return false;
    }


    /**
     * 校验类名显示
     *
     * @param logger logger
     * @return boolean
     */
    private boolean validateClassName(Logger logger) {
        String[] classNames = logOnlineProperties.getClassName();
        if (classNames == null || classNames.length == 0) {
            return true;
        }

        String name = logger.getName();
        for (String className : classNames) {
            if (name.indexOf(className) != -1) {
                return true;
            }
        }
        return false;
    }

}
